Skip to content

chore: prepare release v0.6.0#44

Merged
RISHII7 merged 3 commits into
mainfrom
release/v0.6.0
Jul 2, 2026
Merged

chore: prepare release v0.6.0#44
RISHII7 merged 3 commits into
mainfrom
release/v0.6.0

Conversation

@RISHII7

@RISHII7 RISHII7 commented Jul 2, 2026

Copy link
Copy Markdown
Owner

Release v0.6.0 — Dashboard Module, Sidebar Layout, and UI Library Expansion

What's in this release

Dashboard module — apps/web/modules/dashboard/

  • DashboardLayout server component: reads sidebar_state cookie, composes AuthGuard + OrganizationGuard + SidebarProvider + DashboardSidebar
  • DashboardSidebar client component: OrganizationSwitcher header, three nav groups (Customer Support, Configuration, Account), UserButton footer, SidebarRail, collapsible="icon" mode

Dashboard pages scaffolded
Six stub routes: /conversations, /files, /customization, /integrations, /plugins/vapi, /billing

UI library expansion — packages/ui
40+ new shadcn/ui components, 25 new Radix UI primitives, updated button.tsx / input.tsx / globals.css

App router refactor
app/(dashboard)/layout.tsx now delegates to <DashboardLayout> — guards moved into the module

CI

All checks passed on PR #43 (feature → develop):
Format Check ✅ · Lint ✅ · Type Check ✅ · Build ✅ · Validate PR Title ✅ · CodeQL ✅

🤖 Generated with Claude Code

Summary by CodeRabbit

  • New Features

    • Added a dashboard experience with a collapsible sidebar and several new dashboard pages.
    • Expanded the shared UI library with many new components, including dialogs, menus, tables, forms, charts, and navigation elements.
    • Added mobile detection support and a few new reusable controls like a calendar, carousel, and command palette.
  • Bug Fixes

    • Updated layout and styling tokens to improve consistency across light and dark themes.
    • Refined button and input styling for a more polished, unified interface.

RISHII7 added 2 commits July 2, 2026 11:41
…rary

Introduces the full DashboardLayout/DashboardSidebar module for apps/web
and expands @workspace/ui from ~5 to 40+ shadcn/ui components.

## Dashboard module — apps/web/modules/dashboard/

- DashboardLayout: server component reading sidebar_state cookie for
  SSR-persisted collapse state; composes AuthGuard + OrganizationGuard
  + SidebarProvider + DashboardSidebar + main
- DashboardSidebar: client component with three-section nav
  - Header: OrganizationSwitcher asChild with Clerk appearance tokens
    for sidebar-width and collapsible-icon states
  - Content: Customer Support (Conversations, Knowledge Base),
    Configuration (Widget Customization, Integrations, Voice Assistant),
    Account (Plans & Billing); active-route via usePathname
  - Footer: UserButton showName with Clerk appearance for icon-collapse
  - SidebarRail for drag-to-resize; collapsible=icon mode

## Dashboard pages — apps/web/app/(dashboard)/

Six stub pages scaffolded:
  /conversations, /files, /customization, /integrations,
  /plugins/vapi, /billing

## App router

- app/(dashboard)/layout.tsx: replaced inline AuthGuard +
  OrganizationGuard with single DashboardLayout delegation

## UI library expansion — packages/ui

40+ shadcn/ui components added: accordion, alert-dialog, alert,
aspect-ratio, avatar, badge, breadcrumb, calendar, card, carousel,
chart, checkbox, collapsible, command, context-menu, dialog, drawer,
dropdown-menu, empty, field, hover-card, input-group, input-otp, kbd,
label, menubar, message, native-select, navigation-menu, pagination,
popover, progress, radio-group, resizable, scroll-area, select,
separator, sheet, sidebar, skeleton, slider, sonner, spinner, switch,
table, tabs, textarea, toggle-group, toggle, tooltip

New Radix UI primitives and peer deps: react-accordion,
react-alert-dialog, react-aspect-ratio, react-avatar, react-checkbox,
react-collapsible, react-context-menu, react-dialog,
react-dropdown-menu, react-hover-card, react-label, react-menubar,
react-navigation-menu, react-popover, react-progress, react-radio-group,
react-scroll-area, react-select, react-separator, react-slider,
react-switch, react-tabs, react-toggle, react-toggle-group,
react-tooltip, cmdk, date-fns, embla-carousel-react, input-otp,
react-day-picker, react-resizable-panels, recharts, sonner, vaul

Core updates: button.tsx rewritten, input.tsx updated, globals.css
expanded with sidebar/chart design tokens and Tailwind v4 layer

## Docs

- CHANGELOG.md: v0.6.0 section with full technical detail
- README.md: Dashboard Layout feature, architecture diagram updated,
  design system description updated
#43)

feat(web): add dashboard module, sidebar layout, and expand UI library
@coderabbitai

coderabbitai Bot commented Jul 2, 2026

Copy link
Copy Markdown

Review Change Stack

Warning

Review limit reached

@RISHII7, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 46 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: e8ea3705-fc62-4131-b8ec-47cf5b7be2ba

📥 Commits

Reviewing files that changed from the base of the PR and between d5bf29e and 45fa78a.

📒 Files selected for processing (2)
  • CHANGELOG.md
  • README.md
📝 Walkthrough

Walkthrough

This PR adds a Dashboard module (sidebar client component, async server layout with cookie-persisted state, and six stub route pages), replaces the previous auth/organization guard wrapping in the dashboard root layout with delegation to the new layout, and substantially expands the packages/ui component library with dozens of new Radix-based components, updated dependencies, and revised global design tokens. CHANGELOG and README are updated accordingly.

Changes

Dashboard Layout and Pages

Layer / File(s) Summary
Sidebar and layout composition
apps/web/modules/dashboard/ui/components/dashboard-sidebar/index.tsx, apps/web/modules/dashboard/ui/layouts/dashboard-layout/index.tsx, apps/web/app/(dashboard)/layout.tsx
Adds DashboardSidebar (Clerk org switcher/user button, nav groups, active-route detection) and DashboardLayout (cookie-based SidebarProvider state, guard composition); root dashboard layout now delegates solely to DashboardLayout.
Stub route pages
apps/web/app/(dashboard)/{billing,conversations,customization,files,integrations,plugins/vapi}/page.tsx
Adds minimal default-exported Page components rendering static placeholder text for each dashboard route.

Estimated code review effort: 3 (Moderate) | ~25 minutes

UI Component Library Expansion

Layer / File(s) Summary
Dependencies and global styles
apps/web/package.json, packages/ui/package.json, packages/ui/src/styles/globals.css
Adds numerous Radix/UI runtime dependencies, updates version ranges, removes @base-ui/react/shadcn, and rewrites Tailwind imports plus :root/.dark/@theme inline design tokens and radius formulas.
Core primitives
packages/ui/src/components/{button,input,label,textarea,kbd,spinner,skeleton,separator,badge}.tsx
Refactors Button/Input off @base-ui/react onto native elements with asChild/Slot support; adds Label, Textarea, Kbd, Spinner, Skeleton, Separator, Badge.
Form controls
packages/ui/src/components/{checkbox,radio-group,switch,slider,toggle,toggle-group,select,native-select,input-otp,input-group,field}.tsx
Adds a full set of form-control wrapper components around Radix primitives with variant styling and composable field/error-handling primitives.
Overlay and menu components
packages/ui/src/components/{dialog,alert-dialog,sheet,drawer,popover,hover-card,tooltip,context-menu,dropdown-menu,menubar,command}.tsx
Adds dialog/overlay/menu component families wrapping Radix, vaul, and cmdk primitives with consistent styling and slot attributes.
Display and layout components
packages/ui/src/components/{accordion,alert,avatar,card,breadcrumb,collapsible,empty,message,navigation-menu,pagination,progress,resizable,scroll-area,table,tabs,sidebar,chart,carousel,calendar,sonner,aspect-ratio}.tsx, packages/ui/src/hooks/use-mobile.ts
Adds remaining display/layout components including the full Sidebar system, Chart/Carousel/Calendar wrappers, Sonner Toaster, and a mobile-detection hook.

Estimated code review effort: 4 (Complex) | ~75 minutes

Changelog and README Documentation

Layer / File(s) Summary
Release notes and docs updates
CHANGELOG.md, README.md
Adds a 0.6.0 changelog entry with compare links, and updates README feature bullets and architecture tree/description to include Dashboard and hooks modules.

Estimated code review effort: 1 (Trivial) | ~5 minutes

Possibly related PRs

  • RISHII7/echo#34: Introduced the AuthGuard/OrganizationGuard dashboard layout composition that this PR modifies by delegating to the new DashboardLayout.
🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly matches the PR’s main purpose: preparing the v0.6.0 release.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch release/v0.6.0

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@RISHII7
RISHII7 merged commit b1108c2 into main Jul 2, 2026
7 of 8 checks passed

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 5

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
packages/ui/src/components/aspect-ratio.tsx (1)

1-23: 🎯 Functional Correctness | 🔴 Critical | ⚡ Quick win

Missing React import will break compilation.

React.ComponentProps<"div"> and React.CSSProperties are used but React is never imported in this file, unlike every sibling component (avatar.tsx, popover.tsx, hover-card.tsx all import * as React from "react"). This will fail with "Cannot find namespace 'React'".

🐛 Proposed fix
+import * as React from "react"
+
 import { cn } from "`@workspace/ui/lib/utils`"
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/aspect-ratio.tsx` around lines 1 - 23, The
AspectRatio component references React.ComponentProps and React.CSSProperties
without importing React, which will break compilation. Update the AspectRatio
module to import React the same way as the sibling components, and keep the
existing use of React.ComponentProps<"div"> and React.CSSProperties in the
AspectRatio function unchanged otherwise.
packages/ui/src/components/collapsible.tsx (1)

1-34: 🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

Import React before using React.ComponentProps

packages/ui/src/components/collapsible.tsx uses React.ComponentProps but never imports React. The react-jsx setting covers JSX, not the React type namespace, so this file fails typechecking until the import is added.

🐛 Proposed fix
 "use client"
 
+import * as React from "react"
 import * as CollapsiblePrimitive from "`@radix-ui/react-collapsible`"
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/collapsible.tsx` around lines 1 - 34, The
Collapsible component file uses React.ComponentProps in Collapsible,
CollapsibleTrigger, and CollapsibleContent without bringing React into scope, so
typechecking fails. Add the missing React import at the top of the file and keep
the existing component definitions unchanged so the React type namespace is
available for those props types.
🧹 Nitpick comments (5)
apps/web/modules/dashboard/ui/components/dashboard-sidebar/index.tsx (1)

109-178: 📐 Maintainability & Code Quality | 🔵 Trivial

Extract a reusable SidebarNavGroup to remove duplication.

The three SidebarGroup blocks (Customer Support, Configuration, Account) are structurally identical, differing only in label and item array. Consider a small helper component taking label and items to reduce this to three calls.

Example refactor
+type NavItem = { title: string; url: string; icon: React.ComponentType<{ className?: string }> }
+
+const SidebarNavGroup = ({
+  label,
+  items,
+  isActive,
+}: {
+  label: string
+  items: NavItem[]
+  isActive: (url: string) => boolean
+}) => (
+  <SidebarGroup>
+    <SidebarGroupLabel>{label}</SidebarGroupLabel>
+    <SidebarGroupContent>
+      <SidebarMenu>
+        {items.map((item) => (
+          <SidebarMenuItem key={item.title}>
+            <SidebarMenuButton asChild isActive={isActive(item.url)} tooltip={item.title}>
+              <Link href={item.url}>
+                <item.icon className="size-4" />
+                <span>{item.title}</span>
+              </Link>
+            </SidebarMenuButton>
+          </SidebarMenuItem>
+        ))}
+      </SidebarMenu>
+    </SidebarGroupContent>
+  </SidebarGroup>
+)
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@apps/web/modules/dashboard/ui/components/dashboard-sidebar/index.tsx` around
lines 109 - 178, The three repeated navigation sections inside SidebarContent
are duplicated and should be extracted into a reusable SidebarNavGroup helper.
Create a small component near dashboard-sidebar/index.tsx that takes a label and
items array, and move the shared SidebarGroup, SidebarGroupLabel,
SidebarGroupContent, SidebarMenu, and SidebarMenuItem/SidebarMenuButton
rendering logic into it. Then replace the Customer Support, Configuration, and
Account blocks with three calls using customerSupportItems, configurationItems,
and accountItems.
apps/web/modules/dashboard/ui/layouts/dashboard-layout/index.tsx (1)

20-20: 📐 Maintainability & Code Quality | 🔵 Trivial

Consider an explicit SidebarTrigger for discoverability.

The stock shadcn pattern places <SidebarTrigger /> inside <main> alongside {children}. Here, toggling relies solely on SidebarRail (a thin edge strip) or the Cmd/Ctrl+B shortcut, both less discoverable than an explicit trigger button.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@apps/web/modules/dashboard/ui/layouts/dashboard-layout/index.tsx` at line 20,
The dashboard layout’s main content currently lacks an explicit sidebar toggle,
making the sidebar harder to discover. Update the DashboardLayout component to
render a SidebarTrigger inside the main area alongside the children, following
the standard shadcn pattern. Use the existing DashboardLayout and the main
element in the layout file as the place to add the trigger so users can open the
sidebar without relying only on SidebarRail or the keyboard shortcut.
packages/ui/src/components/field.tsx (1)

118-129: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

FieldTitle reuses data-slot="field-label", colliding with FieldLabel.

FieldTitle (Line 121) is semantically distinct from FieldLabel (Line 107) but shares the same data-slot value. This is a known upstream shadcn/ui issue (tracked as shadcn-ui/ui#8387): using a shared data-slot for different components can cause styling collisions via attribute selectors (e.g. has-[[data-slot=field-label]]) and makes intent unclear. Consider using a unique value like "field-title".

🩹 Proposed fix
 function FieldTitle({ className, ...props }: React.ComponentProps<"div">) {
   return (
     <div
-      data-slot="field-label"
+      data-slot="field-title"
       className={cn(
         "flex w-fit items-center gap-2 text-sm font-medium group-data-[disabled=true]/field:opacity-50",
         className
       )}
       {...props}
     />
   )
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/field.tsx` around lines 118 - 129, `FieldTitle` is
using the same `data-slot="field-label"` value as `FieldLabel`, which creates a
selector collision and makes the two components ambiguous. Update `FieldTitle`
in `field.tsx` to use its own unique data-slot value (for example, a
title-specific slot) and keep `FieldLabel` unchanged so the two components
remain distinguishable by attribute selectors.
packages/ui/src/components/label.tsx (1)

7-18: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Use LabelPrimitive.Root here

packages/ui/package.json already includes @radix-ui/react-label, but packages/ui/src/components/label.tsx still renders a native <label>. If this component is meant to match the new Radix primitives, switch it to LabelPrimitive.Root so it keeps the same label behavior as the rest of the set.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/label.tsx` around lines 7 - 18, The Label
component still renders a native label instead of the Radix primitive. Update
the Label component in label.tsx to use LabelPrimitive.Root from
`@radix-ui/react-label`, keeping the existing props, className handling, and
data-slot behavior intact so it matches the rest of the Radix-based UI
primitives.
packages/ui/src/components/tooltip.tsx (1)

21-29: 🚀 Performance & Scalability | 🔵 Trivial | 💤 Low value

Redundant TooltipProvider nesting.

Tooltip always wraps itself in a new TooltipProvider. Since SidebarProvider (packages/ui/src/components/sidebar.tsx:131) already wraps the tree in a TooltipProvider, every SidebarMenuButton tooltip (sidebar.tsx:536-544) creates a redundant nested provider. Harmless functionally, but unnecessary re-instantiation on a hot path (menu items).

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/tooltip.tsx` around lines 21 - 29, The Tooltip
component currently creates a new TooltipProvider every time Tooltip renders,
which causes redundant nested providers when it’s used inside SidebarProvider.
Update Tooltip in tooltip.tsx so it no longer always instantiates its own
provider; instead, rely on the existing TooltipProvider from the surrounding
tree (such as SidebarProvider) and keep TooltipPrimitive.Root focused on
rendering the tooltip itself. Use Tooltip and TooltipProvider as the key symbols
when making the change.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/ui/src/components/carousel.tsx`:
- Around line 96-105: The `useEffect` in `Carousel` registers both `reInit` and
`select` handlers on `api`, but the cleanup only unsubscribes `select`, so the
`reInit` listener can leak across re-renders and unmounts. Update the cleanup in
`Carousel`’s effect to remove every listener added in the setup path, using the
same `onSelect` callback for both `api.on` subscriptions so the corresponding
`api.off` calls stay consistent.

In `@packages/ui/src/components/drawer.tsx`:
- Around line 32-46: The DrawerOverlay in drawer.tsx is using invalid Tailwind
data variants, so the open/closed animation classes will never apply. Update the
className in DrawerOverlay to use the same data attribute variant syntax
supported elsewhere in this codebase, or define custom variants that match the
attribute Vaul sets on DrawerPrimitive.Overlay. Keep the change localized to
DrawerOverlay and verify the fade/animate classes are driven by the actual data
attribute names.

In `@packages/ui/src/components/empty.tsx`:
- Around line 71-82: EmptyDescription is typed as paragraph props but renders a
div, so align the component’s prop type with its actual element or change the
element to match the semantic description text usage. Update the
EmptyDescription component signature and its JSX in the empty.tsx component so
the rendered tag and React.ComponentProps type are consistent, and keep the
data-slot/className behavior unchanged.
- Around line 1-4: The empty component module uses React.ComponentProps without
importing React, so add the React namespace import at the top of empty.tsx.
Update the imports in the component file that defines the Empty-related types
and props so React.ComponentProps resolves correctly, alongside the existing cva
and cn imports.

In `@packages/ui/src/components/menubar.tsx`:
- Around line 219-241: The MenubarSubTrigger component is using outline-none,
which drops the forced-colors/high-contrast focus ring; update the className in
MenubarSubTrigger to use outline-hidden instead, matching the other menubar item
components and preserving the same focus behavior.

---

Outside diff comments:
In `@packages/ui/src/components/aspect-ratio.tsx`:
- Around line 1-23: The AspectRatio component references React.ComponentProps
and React.CSSProperties without importing React, which will break compilation.
Update the AspectRatio module to import React the same way as the sibling
components, and keep the existing use of React.ComponentProps<"div"> and
React.CSSProperties in the AspectRatio function unchanged otherwise.

In `@packages/ui/src/components/collapsible.tsx`:
- Around line 1-34: The Collapsible component file uses React.ComponentProps in
Collapsible, CollapsibleTrigger, and CollapsibleContent without bringing React
into scope, so typechecking fails. Add the missing React import at the top of
the file and keep the existing component definitions unchanged so the React type
namespace is available for those props types.

---

Nitpick comments:
In `@apps/web/modules/dashboard/ui/components/dashboard-sidebar/index.tsx`:
- Around line 109-178: The three repeated navigation sections inside
SidebarContent are duplicated and should be extracted into a reusable
SidebarNavGroup helper. Create a small component near
dashboard-sidebar/index.tsx that takes a label and items array, and move the
shared SidebarGroup, SidebarGroupLabel, SidebarGroupContent, SidebarMenu, and
SidebarMenuItem/SidebarMenuButton rendering logic into it. Then replace the
Customer Support, Configuration, and Account blocks with three calls using
customerSupportItems, configurationItems, and accountItems.

In `@apps/web/modules/dashboard/ui/layouts/dashboard-layout/index.tsx`:
- Line 20: The dashboard layout’s main content currently lacks an explicit
sidebar toggle, making the sidebar harder to discover. Update the
DashboardLayout component to render a SidebarTrigger inside the main area
alongside the children, following the standard shadcn pattern. Use the existing
DashboardLayout and the main element in the layout file as the place to add the
trigger so users can open the sidebar without relying only on SidebarRail or the
keyboard shortcut.

In `@packages/ui/src/components/field.tsx`:
- Around line 118-129: `FieldTitle` is using the same `data-slot="field-label"`
value as `FieldLabel`, which creates a selector collision and makes the two
components ambiguous. Update `FieldTitle` in `field.tsx` to use its own unique
data-slot value (for example, a title-specific slot) and keep `FieldLabel`
unchanged so the two components remain distinguishable by attribute selectors.

In `@packages/ui/src/components/label.tsx`:
- Around line 7-18: The Label component still renders a native label instead of
the Radix primitive. Update the Label component in label.tsx to use
LabelPrimitive.Root from `@radix-ui/react-label`, keeping the existing props,
className handling, and data-slot behavior intact so it matches the rest of the
Radix-based UI primitives.

In `@packages/ui/src/components/tooltip.tsx`:
- Around line 21-29: The Tooltip component currently creates a new
TooltipProvider every time Tooltip renders, which causes redundant nested
providers when it’s used inside SidebarProvider. Update Tooltip in tooltip.tsx
so it no longer always instantiates its own provider; instead, rely on the
existing TooltipProvider from the surrounding tree (such as SidebarProvider) and
keep TooltipPrimitive.Root focused on rendering the tooltip itself. Use Tooltip
and TooltipProvider as the key symbols when making the change.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 79bbc63d-eeb7-4dfb-a5c3-d605b68b681f

📥 Commits

Reviewing files that changed from the base of the PR and between 94f8915 and d5bf29e.

⛔ Files ignored due to path filters (1)
  • pnpm-lock.yaml is excluded by !**/pnpm-lock.yaml
📒 Files selected for processing (67)
  • CHANGELOG.md
  • README.md
  • apps/web/app/(dashboard)/billing/page.tsx
  • apps/web/app/(dashboard)/conversations/page.tsx
  • apps/web/app/(dashboard)/customization/page.tsx
  • apps/web/app/(dashboard)/files/page.tsx
  • apps/web/app/(dashboard)/integrations/page.tsx
  • apps/web/app/(dashboard)/layout.tsx
  • apps/web/app/(dashboard)/plugins/vapi/page.tsx
  • apps/web/modules/dashboard/ui/components/dashboard-sidebar/index.tsx
  • apps/web/modules/dashboard/ui/layouts/dashboard-layout/index.tsx
  • apps/web/package.json
  • packages/ui/package.json
  • packages/ui/src/components/accordion.tsx
  • packages/ui/src/components/alert-dialog.tsx
  • packages/ui/src/components/alert.tsx
  • packages/ui/src/components/aspect-ratio.tsx
  • packages/ui/src/components/avatar.tsx
  • packages/ui/src/components/badge.tsx
  • packages/ui/src/components/breadcrumb.tsx
  • packages/ui/src/components/button.tsx
  • packages/ui/src/components/calendar.tsx
  • packages/ui/src/components/card.tsx
  • packages/ui/src/components/carousel.tsx
  • packages/ui/src/components/chart.tsx
  • packages/ui/src/components/checkbox.tsx
  • packages/ui/src/components/collapsible.tsx
  • packages/ui/src/components/command.tsx
  • packages/ui/src/components/context-menu.tsx
  • packages/ui/src/components/dialog.tsx
  • packages/ui/src/components/drawer.tsx
  • packages/ui/src/components/dropdown-menu.tsx
  • packages/ui/src/components/empty.tsx
  • packages/ui/src/components/field.tsx
  • packages/ui/src/components/hover-card.tsx
  • packages/ui/src/components/input-group.tsx
  • packages/ui/src/components/input-otp.tsx
  • packages/ui/src/components/input.tsx
  • packages/ui/src/components/kbd.tsx
  • packages/ui/src/components/label.tsx
  • packages/ui/src/components/menubar.tsx
  • packages/ui/src/components/message.tsx
  • packages/ui/src/components/native-select.tsx
  • packages/ui/src/components/navigation-menu.tsx
  • packages/ui/src/components/pagination.tsx
  • packages/ui/src/components/popover.tsx
  • packages/ui/src/components/progress.tsx
  • packages/ui/src/components/radio-group.tsx
  • packages/ui/src/components/resizable.tsx
  • packages/ui/src/components/scroll-area.tsx
  • packages/ui/src/components/select.tsx
  • packages/ui/src/components/separator.tsx
  • packages/ui/src/components/sheet.tsx
  • packages/ui/src/components/sidebar.tsx
  • packages/ui/src/components/skeleton.tsx
  • packages/ui/src/components/slider.tsx
  • packages/ui/src/components/sonner.tsx
  • packages/ui/src/components/spinner.tsx
  • packages/ui/src/components/switch.tsx
  • packages/ui/src/components/table.tsx
  • packages/ui/src/components/tabs.tsx
  • packages/ui/src/components/textarea.tsx
  • packages/ui/src/components/toggle-group.tsx
  • packages/ui/src/components/toggle.tsx
  • packages/ui/src/components/tooltip.tsx
  • packages/ui/src/hooks/use-mobile.ts
  • packages/ui/src/styles/globals.css

Comment on lines +96 to +105
React.useEffect(() => {
if (!api) return
onSelect(api)
api.on("reInit", onSelect)
api.on("select", onSelect)

return () => {
api?.off("select", onSelect)
}
}, [api, onSelect])

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🩺 Stability & Availability | 🟡 Minor | ⚡ Quick win

Missing cleanup for reInit listener.

Both "reInit" and "select" listeners are registered, but only "select" is removed in the cleanup function, leaking the reInit listener on every effect re-run/unmount.

🔧 Proposed fix
     return () => {
+      api?.off("reInit", onSelect)
       api?.off("select", onSelect)
     }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
React.useEffect(() => {
if (!api) return
onSelect(api)
api.on("reInit", onSelect)
api.on("select", onSelect)
return () => {
api?.off("select", onSelect)
}
}, [api, onSelect])
React.useEffect(() => {
if (!api) return
onSelect(api)
api.on("reInit", onSelect)
api.on("select", onSelect)
return () => {
api?.off("reInit", onSelect)
api?.off("select", onSelect)
}
}, [api, onSelect])
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/carousel.tsx` around lines 96 - 105, The
`useEffect` in `Carousel` registers both `reInit` and `select` handlers on
`api`, but the cleanup only unsubscribes `select`, so the `reInit` listener can
leak across re-renders and unmounts. Update the cleanup in `Carousel`’s effect
to remove every listener added in the setup path, using the same `onSelect`
callback for both `api.on` subscriptions so the corresponding `api.off` calls
stay consistent.

Comment on lines +32 to +46
function DrawerOverlay({
className,
...props
}: React.ComponentProps<typeof DrawerPrimitive.Overlay>) {
return (
<DrawerPrimitive.Overlay
data-slot="drawer-overlay"
className={cn(
"fixed inset-0 z-50 bg-black/10 data-closed:animate-out data-closed:fade-out-0 data-open:animate-in data-open:fade-in-0 supports-backdrop-filter:backdrop-blur-xs",
className
)}
{...props}
/>
)
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🌐 Web query:

Does vaul Drawer.Overlay component set data-state attribute like Radix Dialog?

💡 Result:

The Vaul Drawer.Overlay component does not use the standard data-state attribute (i.e., data-state="open" or data-state="closed") found in Radix UI primitives [1][2]. While Vaul is built on top of Radix UI's Dialog primitive [3], the Vaul implementation overrides the behavior of the overlay for its own custom state management [1][2]. Instead of the standard Radix data-state attribute, the Drawer.Overlay component uses a set of custom data attributes, including [1]: data-vaul-overlay="" data-vaul-snap-points data-vaul-snap-points-overlay data-vaul-animate Because Vaul does not expose the standard Radix data-state on its overlay, developers who wish to use CSS selectors like [data-state=open] to style the overlay must either apply those attributes manually or use a wrapper that adds them based on the drawer's state [4]. The absence of this native attribute has been a subject of discussion within the Vaul community, with some users noting the desire for standard data attributes to simplify integration with utility-first CSS frameworks like Tailwind CSS [5].

Citations:


🏁 Script executed:

#!/bin/bash
set -euo pipefail

git ls-files packages/ui/src/components/drawer.tsx packages/ui/package.json package.json
echo '--- drawer.tsx ---'
cat -n packages/ui/src/components/drawer.tsx
echo '--- package.json (ui) ---'
cat -n packages/ui/package.json
echo '--- root package.json ---'
cat -n package.json

Repository: RISHII7/echo

Length of output: 9416


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo '--- search data-open / data-closed usage ---'
rg -n --hidden --glob '!**/node_modules/**' 'data-(open|closed):|data-\[state=' packages root package.json package.json tailwind.config.* postcss.config.* 2>/dev/null || true

echo '--- locate Tailwind config / css entrypoints ---'
git ls-files | rg 'tailwind|postcss|globals\.css|\.css$'

echo '--- inspect relevant styling files ---'
for f in $(git ls-files | rg 'tailwind|postcss|globals\.css|\.css$'); do
  echo "--- $f ---"
  wc -l "$f"
done

Repository: RISHII7/echo

Length of output: 17543


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo '--- packages/ui/postcss.config.mjs ---'
cat -n packages/ui/postcss.config.mjs

echo '--- packages/ui/src/styles/globals.css ---'
sed -n '1,220p' packages/ui/src/styles/globals.css

echo '--- search for custom data-open/data-closed variant definitions ---'
rg -n --hidden --glob '!**/node_modules/**' 'data-open|data-closed|addVariant|`@custom-variant`|custom-variant' packages/ui apps

Repository: RISHII7/echo

Length of output: 5139


🌐 Web query:

vaul 1.1.2 Drawer.Overlay data-state data-vaul-overlay source

💡 Result:

In Vaul 1.1.2, Drawer.Overlay is a component that renders a backdrop layer covering the inert portion of the view when the drawer is open [1][2]. It is intended to be used within the Drawer.Portal component [3][2]. Styling hooks for the overlay are exposed via specific data attributes that allow for CSS targeting [3]. The primary attribute is data-vaul-overlay, which is applied to the overlay element to facilitate custom styling [3]. Historically, older versions or internal implementations used attributes like vaul-overlay or vaul-snap-points-overlay [4][5], but standard usage in recent versions of Vaul relies on data-vaul-* attributes for CSS selectors [3]. These attributes are automatically managed by the drawer state (e.g., open/closed status or snap point transitions) [3][4]. If you are attempting to style the overlay, you should target the [data-vaul-overlay] attribute in your CSS [3]. Example CSS: [data-vaul-overlay] { background: rgba(0, 0, 0, 0.4); } Example usage in JSX: <Drawer.Portal> <Drawer.Overlay /> <Drawer.Content> {/* Drawer Content */} </Drawer.Content> </Drawer.Portal>

Citations:


🌐 Web query:

vaul Drawer.Overlay source data-vaul-overlay data-state site:github.com/emilkowalski/vaul

💡 Result:

In Vaul, the Drawer.Overlay component and other drawer elements utilize standard data attributes to reflect their current state and configuration, which facilitates styling via CSS or utility frameworks like Tailwind CSS [1][2]. The data-state attribute is used to track the visibility and animation status of the drawer components. It typically takes the values "open" or "closed" [3]. Regarding data-vaul- attributes: - Following updates to align with standard data attribute practices, internal Vaul attributes were renamed from custom prefixed attributes (like vaul-drawer) to prefixed data attributes (e.g., data-vaul-drawer, data-vaul-drawer-direction) [1][2]. - These attributes allow you to target specific drawer states and directions in your CSS [1]. For example, you can use data-[vaul-drawer-direction=right] to apply conditional styling based on the drawer's direction [1]. - The Drawer.Overlay component is rendered internally and can be styled directly, although it is often managed as part of the Drawer.Content structure [4][5]. These data attributes are designed to be consistent with conventions used by other UI libraries (such as Radix UI), making them predictable for developers using Tailwind CSS data attribute selectors [1][6].

Citations:


🌐 Web query:

Tailwind CSS data-open variant data-closed variant support

💡 Result:

Tailwind CSS provides robust, built-in support for styling elements based on data attributes through its data-* variant system [1][2][3]. Arbitrary Data Attribute Variants You can use the data-* variant syntax to target any data attribute dynamically without additional configuration [1][3]. The syntax follows the pattern data-[attribute=value] [1][3]. Examples: - To target an element where data-open="true": class="data-[open=true]:bg-blue-500" - To target an element where data-state="closed": class="data-[state=closed]:hidden" This approach also supports group and peer modifiers to style child or sibling elements based on a parent's or peer's data attribute state [1][4]: - Group example: class="group-data-[open=true]:block" - Peer example: class="peer-data-[state=closed]:opacity-50" Configuration (Optional) If you frequently use specific data attributes, you can define shortcuts in your tailwind.config.js (or equivalent configuration) under the theme.data section [1][3]. This allows for cleaner utility classes [1]: // tailwind.config.js example module.exports = { theme: { data: { open: 'state~="open"', closed: 'state~="closed"', }, }, } // Resulting usage:

...
Tailwind v4 Custom Variants In Tailwind CSS v4, you can also define custom variants using the @custom-variant directive in your CSS, which provides more control for complex state selectors [5]: @custom-variant open (&[data-state="open"]); @custom-variant closed (&[data-state="closed"]); /* Usage */
...
These features allow you to move away from manual class-toggling in JavaScript, enabling you to drive component visuals directly from semantic HTML data attributes [2].

Citations:


Use a valid Tailwind data variant here data-open: / data-closed: aren’t defined in this setup, so the overlay fade classes won’t match. Switch to the data-[...] form used elsewhere here, or add custom variants for the attribute Vaul exposes.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/drawer.tsx` around lines 32 - 46, The
DrawerOverlay in drawer.tsx is using invalid Tailwind data variants, so the
open/closed animation classes will never apply. Update the className in
DrawerOverlay to use the same data attribute variant syntax supported elsewhere
in this codebase, or define custom variants that match the attribute Vaul sets
on DrawerPrimitive.Overlay. Keep the change localized to DrawerOverlay and
verify the fade/animate classes are driven by the actual data attribute names.

Comment on lines +1 to +4
import { cva, type VariantProps } from "class-variance-authority"

import { cn } from "@workspace/ui/lib/utils"

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟠 Major | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

printf '\n== file ==\n'
cat -n packages/ui/src/components/empty.tsx

printf '\n== tsconfig candidates ==\n'
git ls-files '*/tsconfig*.json' 'tsconfig*.json'

printf '\n== search for React.ComponentProps usage and import style ==\n'
rg -n 'React\.ComponentProps|import \* as React from "react"|import type \* as React from "react"|type ComponentProps' packages/ui/src/components -g '*.tsx' -g '*.ts'

Repository: RISHII7/echo

Length of output: 35036


Import React for React.ComponentProps
packages/ui/src/components/empty.tsx uses React.ComponentProps in several places, but React is never imported. Add import * as React from "react" at the top.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/empty.tsx` around lines 1 - 4, The empty component
module uses React.ComponentProps without importing React, so add the React
namespace import at the top of empty.tsx. Update the imports in the component
file that defines the Empty-related types and props so React.ComponentProps
resolves correctly, alongside the existing cva and cn imports.

Comment on lines +71 to +82
function EmptyDescription({ className, ...props }: React.ComponentProps<"p">) {
return (
<div
data-slot="empty-description"
className={cn(
"text-sm/relaxed text-muted-foreground [&>a]:underline [&>a]:underline-offset-4 [&>a:hover]:text-primary",
className
)}
{...props}
/>
)
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

EmptyDescription typed as <p> props but renders a <div>.

The prop type promises React.ComponentProps<"p"> while the actual element is a <div>, allowing paragraph-only attributes to be spread onto a div and diverging from the typical semantic <p> used for description text.

🛠️ Proposed fix
-function EmptyDescription({ className, ...props }: React.ComponentProps<"p">) {
+function EmptyDescription({ className, ...props }: React.ComponentProps<"p">) {
   return (
-    <div
+    <p
       data-slot="empty-description"
       className={cn(
         "text-sm/relaxed text-muted-foreground [&>a]:underline [&>a]:underline-offset-4 [&>a:hover]:text-primary",
         className
       )}
       {...props}
-    />
+    />
   )
 }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
function EmptyDescription({ className, ...props }: React.ComponentProps<"p">) {
return (
<div
data-slot="empty-description"
className={cn(
"text-sm/relaxed text-muted-foreground [&>a]:underline [&>a]:underline-offset-4 [&>a:hover]:text-primary",
className
)}
{...props}
/>
)
}
function EmptyDescription({ className, ...props }: React.ComponentProps<"p">) {
return (
<p
data-slot="empty-description"
className={cn(
"text-sm/relaxed text-muted-foreground [&>a]:underline [&>a]:underline-offset-4 [&>a:hover]:text-primary",
className
)}
{...props}
/>
)
}
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/empty.tsx` around lines 71 - 82, EmptyDescription
is typed as paragraph props but renders a div, so align the component’s prop
type with its actual element or change the element to match the semantic
description text usage. Update the EmptyDescription component signature and its
JSX in the empty.tsx component so the rendered tag and React.ComponentProps type
are consistent, and keep the data-slot/className behavior unchanged.

Comment on lines +219 to +241
function MenubarSubTrigger({
className,
inset,
children,
...props
}: React.ComponentProps<typeof MenubarPrimitive.SubTrigger> & {
inset?: boolean
}) {
return (
<MenubarPrimitive.SubTrigger
data-slot="menubar-sub-trigger"
data-inset={inset}
className={cn(
"flex cursor-default items-center rounded-sm px-2 py-1.5 text-sm outline-none select-none focus:bg-accent focus:text-accent-foreground data-inset:pl-8 data-[state=open]:bg-accent data-[state=open]:text-accent-foreground",
className
)}
{...props}
>
{children}
<ChevronRightIcon className="ml-auto h-4 w-4" />
</MenubarPrimitive.SubTrigger>
)
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🎯 Functional Correctness | 🟡 Minor | ⚡ Quick win

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
set -euo pipefail

printf 'FILE: packages/ui/src/components/menubar.tsx\n'
nl -ba packages/ui/src/components/menubar.tsx | sed -n '45,260p'

printf '\nUSAGE OF outline-hidden / outline-none IN FILE:\n'
rg -n 'outline-(hidden|none)' packages/ui/src/components/menubar.tsx

printf '\nRELEVANT PACKAGE INFO:\n'
for f in package.json packages/ui/package.json pnpm-workspace.yaml; do
  if [ -f "$f" ]; then
    echo "--- $f"
    sed -n '1,220p' "$f" | rg -n '"tailwindcss"|outline-hidden|outline-none|version|dependencies|devDependencies' -n -C 1 || true
  fi
done

printf '\nTAILWIND REFERENCES IN REPO:\n'
rg -n '"tailwindcss"|outline-hidden|outline-none' . --glob '!**/node_modules/**' --glob '!**/dist/**' --glob '!**/build/**' | sed -n '1,200p'

Repository: RISHII7/echo

Length of output: 235


🌐 Web query:

Tailwind CSS v4 outline-none outline-hidden forced-colors high contrast accessibility documentation

💡 Result:

In Tailwind CSS v4, the handling of outline utilities has been updated to improve clarity and accessibility compliance [1][2]. Key changes include: 1. Renaming and New Utilities: The former outline-none utility (which provided an invisible 2px outline to preserve accessibility in forced-colors mode) has been renamed to outline-hidden [1][2]. A new, literal outline-none utility has been introduced that simply sets outline-style: none [1][2]. 2. outline-hidden and Accessibility: The outline-hidden utility is preferred when you need to hide an outline while maintaining accessibility standards [3]. It is specifically designed to ensure that focus indicators remain visible when the user has forced-colors mode (high contrast mode) enabled in their browser or operating system [2][3]. 3. Forced-Colors Support: Tailwind CSS v4 includes native support for the forced-colors media feature [4][5]. Beyond outline-hidden, you can use the forced-color-adjust utility (mapped to the CSS forced-color-adjust property) to control how elements behave in high contrast environments [6][5]. When building for accessibility, it is recommended to use outline-hidden if your intention is to replace the default browser focus ring with a custom design (e.g., using box shadows), as this ensures the focus remains perceivable for all users [2]. Use the new outline-none with caution, as it will remove the focus indicator entirely, which can lead to accessibility issues unless you have implemented an alternative, highly visible focus state [2].

Citations:


🌐 Web query:

shadcn-ui/ui issue 10101 MenubarSubTrigger outline-none outline-hidden

💡 Result:

The issue #10101 in the shadcn-ui/ui repository concerns an accessibility inconsistency where components, including MenubarSubTrigger, were using outline-none in the v4 registry instead of outline-hidden [1][2]. In Tailwind CSS and web development, outline-none removes the focus outline entirely, which can negatively impact accessibility by making components difficult or impossible to identify for keyboard users and those utilizing assistive technologies [2]. In contrast, outline-hidden is designed to be used in conjunction with high-contrast/forced-colors modes, ensuring that the focus indicator remains visible and accessible in those environments while appearing hidden in others [2]. This issue was addressed by pull request #10102, which proposed replacing all occurrences of outline-none with outline-hidden across the v4 registry files to ensure consistency and improve accessibility [2]. If you are experiencing this issue, you can resolve it by manually updating the className properties in your local copy of the component to use outline-hidden [2].

Citations:


🏁 Script executed:

# No-op placeholder to keep investigation focused on the retrieved outputs.

Repository: RISHII7/echo

Length of output: 150


Use outline-hidden for MenubarSubTrigger. outline-none removes the forced-colors/high-contrast focus ring in Tailwind v4; outline-hidden matches the other menubar items.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/ui/src/components/menubar.tsx` around lines 219 - 241, The
MenubarSubTrigger component is using outline-none, which drops the
forced-colors/high-contrast focus ring; update the className in
MenubarSubTrigger to use outline-hidden instead, matching the other menubar item
components and preserving the same focus behavior.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant